home *** CD-ROM | disk | FTP | other *** search
/ Personal Computer World 2007 September / PCWSEP07.iso / Software / Linux / Linux Mint 3.0 Light / LinuxMint-3.0-Light.iso / casper / filesystem.squashfs / usr / lib / hplip / base / msg.py < prev    next >
Encoding:
Python Source  |  2007-04-04  |  7.2 KB  |  274 lines

  1. # -*- coding: utf-8 -*-
  2. #
  3. # (c) Copyright 2003-2007 Hewlett-Packard Development Company, L.P.
  4. #
  5. # This program is free software; you can redistribute it and/or modify
  6. # it under the terms of the GNU General Public License as published by
  7. # the Free Software Foundation; either version 2 of the License, or
  8. # (at your option) any later version.
  9. #
  10. # This program is distributed in the hope that it will be useful,
  11. # but WITHOUT ANY WARRANTY; without even the implied warranty of
  12. # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  13. # GNU General Public License for more details.
  14. #
  15. # You should have received a copy of the GNU General Public License
  16. # along with this program; if not, write to the Free Software
  17. # Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
  18. #
  19. # Author: Don Welch
  20. #
  21.  
  22.  
  23. # Std Lib
  24. import sys, cStringIO, select, socket
  25.  
  26. # Local
  27. from g import *
  28. from codes import *
  29.  
  30. #valid_encodings = ('', 'none', 'base64')
  31. #valid_char_encodings = ('', 'utf-8', 'latin-1')
  32.  
  33.  
  34. def buildResultMessage(msg_type, payload=None, result_code=ERROR_SUCCESS, other_fields={}):
  35.     other_fields.update({'result-code' : result_code})
  36.     return buildMessage(msg_type, payload, other_fields)
  37.  
  38. def buildMessage(msg_type, payload=None, other_fields={}):
  39.  
  40.     if msg_type is None or not msg_type:
  41.         raise Error(ERROR_INVALID_MSG_TYPE)
  42.  
  43.     msg = cStringIO.StringIO()
  44.     msg.write("msg=%s\n" % msg_type.lower())
  45.  
  46.     if other_fields:
  47.         for k in other_fields:
  48.             msg.write('%s=%s\n' % (k, str(other_fields[k])))
  49.  
  50.     if payload is not None:
  51.         #msg.write("encoding=none\n")
  52.         msg.write("length=%d\n" % len(str(payload)))
  53.         msg.write("data:\n%s" % str(payload))
  54.  
  55.     return msg.getvalue()
  56.  
  57.  
  58. def parseMessage(message):
  59.     fields, data_found, data, remaining_msg = {}, False, '', ''
  60.     msg_key_found, second_msg_key = False, False
  61.  
  62.     try:
  63.         msg = cStringIO.StringIO(message)
  64.     except TypeError:
  65.         raise Error(ERROR_INVALID_MSG_TYPE)
  66.  
  67.     while True:
  68.         pos = msg.tell()
  69.         line = msg.readline().strip()
  70.  
  71.         if line == "":
  72.             break
  73.  
  74.         if line.startswith('data:'):
  75.             data = msg.read(fields['length']) or ''
  76.             data_found = True
  77.             continue
  78.  
  79.         if line.startswith('#'):
  80.             continue
  81.  
  82.         try:
  83.             key, value = line.split('=', 1)
  84.             key = key.strip().lower()
  85.         except ValueError:
  86.             raise Error(ERROR_INVALID_MSG_TYPE)
  87.  
  88.         if key == 'msg':
  89.             if msg_key_found:
  90.                 # already found, another message...
  91.                 second_msg_key = True
  92.                 break
  93.             else:
  94.                 msg_key_found = True
  95.  
  96.         # If it looks like a number, convert it, otherwise leave it alone
  97.         try:
  98.             fields[key] = int(value)
  99.         except ValueError:
  100.             fields[key] = value
  101.  
  102.     if second_msg_key:
  103.         msg.seek(pos)
  104.         remaining_msg = msg.read() or ''
  105.  
  106.     return fields, data, remaining_msg
  107.  
  108.  
  109. def sendEvent(sock, msg_type, payload=None, other_fields={}, 
  110.               timeout=prop.read_timeout):
  111.  
  112.     m = buildMessage(msg_type, payload, other_fields)
  113.  
  114.     log.debug("Sending data on channel (%d)" % sock.fileno())
  115.     log.debug(repr(m))
  116.  
  117.     r, w, e = select.select([], [sock], [], timeout)
  118.  
  119.     if w == []:
  120.         raise Error(ERROR_INTERNAL)
  121.  
  122.     try:
  123.         sock.send(m)
  124.     except socket.error:
  125.         log.exception()
  126.         raise Error(ERROR_INTERNAL)
  127.  
  128.  
  129. def xmitMessage(sock, msg_type, payload=None,
  130.                  other_fields={},
  131.                  timeout=prop.read_timeout):
  132.  
  133.     fields, data, result_code = {}, '', ERROR_INTERNAL
  134.  
  135.     msg_type = msg_type.lower().strip()
  136.     m = buildMessage(msg_type, payload, other_fields)
  137.  
  138.     log.debug("(xmit) Sending data on channel (%d)" % sock.fileno())
  139.     log.debug(repr(m))
  140.  
  141.     r, w, e = select.select([], [sock], [], timeout)
  142.  
  143.     if w == []:
  144.         raise Error(ERROR_INTERNAL)
  145.  
  146.     try:
  147.         sock.send(m)
  148.     except socket.error:
  149.         log.exception()
  150.         raise Error(ERROR_INTERNAL)
  151.  
  152.     read_tries = 0
  153.     read_flag = True
  154.  
  155.     while read_flag:
  156.         remaining = ''
  157.         read_tries += 1
  158.  
  159.         if read_tries > 3:
  160.             break
  161.  
  162.         r, w, e = select.select([sock], [], [], timeout)
  163.  
  164.         if r == []:
  165.             raise Error(ERROR_INTERNAL)
  166.  
  167.         m = sock.recv(prop.max_message_read)
  168.  
  169.         if m == '':
  170.             continue
  171.  
  172.         log.debug("(xmit) Reading data on channel (%d)" % sock.fileno())
  173.  
  174.         while True:
  175.             log.debug(repr(m))
  176.             fields, data, remaining = parseMessage(m)
  177.  
  178.             try:
  179.                 result_code = fields['result-code']
  180.             except KeyError:
  181.                 result_code = ERROR_INTERNAL
  182.             else:
  183.                 del fields['result-code']
  184.  
  185.             try:
  186.                 result_msg_type = fields['msg'].lower().strip()
  187.             except KeyError:
  188.                 result_msg_type = ''
  189.             else:
  190.                 del fields['msg']
  191.  
  192.             # Found the msg we were looking for or error
  193.             if result_msg_type == ''.join([msg_type, 'result']) or \
  194.                 result_msg_type == 'messageerror': 
  195.                 read_flag = False # exit read loop
  196.                 break
  197.             else:
  198.                 log.debug("Ignored out of sequence message")
  199.  
  200.             if remaining: # more messages to look at in this read
  201.                 log.debug("Remaining message")
  202.                 m = remaining # parse remainder
  203.             else:
  204.                 # keep reading until we find the result msg...
  205.                 break
  206.  
  207.  
  208.     return fields, data, result_code
  209.  
  210.  
  211.  
  212.  
  213. def recvMessage(sock, timeout=prop.read_timeout):
  214.     fields, data, result_code = {}, '', ERROR_INTERNAL
  215.  
  216.     read_tries = 0
  217.     read_flag = True
  218.  
  219.     while read_flag:
  220.         remaining = ''
  221.         read_tries += 1
  222.  
  223.         if read_tries > 3:
  224.             break
  225.  
  226.         r, w, e = select.select([sock], [], [], timeout)
  227.  
  228.         if r == []:
  229.             #raise Error(ERROR_INTERNAL)
  230.             continue
  231.  
  232.         m = sock.recv(prop.max_message_read)
  233.  
  234.         if m == '':
  235.             continue
  236.  
  237.         log.debug("(xmit) Reading data on channel (%d)" % sock.fileno())
  238.  
  239.         while True:
  240.             log.debug(repr(m))
  241.             fields, data, remaining = parseMessage(m)
  242.  
  243.             try:
  244.                 result_code = fields['result-code']
  245.             except KeyError:
  246.                 result_code = ERROR_INTERNAL
  247.             else:
  248.                 del fields['result-code']
  249.  
  250.             try:
  251.                 result_msg_type = fields['msg'].lower().strip()
  252.             except KeyError:
  253.                 result_msg_type = ''
  254.             else:
  255.                 del fields['msg']
  256.  
  257.             # Found the msg we were looking for or error
  258.             #if result_msg_type == ''.join([msg_type, 'result']) or \
  259.             if result_msg_type == 'messageerror': 
  260.                 read_flag = False # exit read loop
  261.                 break
  262.             #else:
  263.             #    log.debug("Ignored out of sequence message")
  264.  
  265.             if remaining: # more messages to look at in this read
  266.                 log.debug("Remaining message")
  267.                 m = remaining # parse remainder
  268.             else:
  269.                 # keep reading until we find the result msg...
  270.                 break    
  271.  
  272.     return fields, data, result_code
  273.  
  274.